<template>
  <a-card :bordered="false">
    <div class="table-operator">
      <a-button type="primary" icon="plus" @click="openAddModal">新增菜单</a-button>
      <a-button icon="reload" style="margin-left: 8px" @click="loadMenuTree">刷新</a-button>
    </div>
    <a-table
      :columns="columns"
      :dataSource="menuTree"
      :loading="loading"
      rowKey="id"
      :pagination="false"
      :defaultExpandAllRows="true"
      :childrenColumnName="'children'"
      bordered
    >
      <span slot="status" slot-scope="text, record">
        <a-switch :checked="record.status === 1" :loading="record && record.statusLoading || false" @change="onStatusChange(record, $event)" />
      </span>
      <span slot="issort" slot-scope="text">
        <a-tag :color="text === 1 ? 'blue' : 'green'">{{ text === 1 ? '分类' : '菜单' }}</a-tag>
      </span>
      <span slot="isdev" slot-scope="text">
        <a-tag :color="text === 1 ? 'orange' : ''">{{ text === 1 ? '开发者可见' : '全部可见' }}</a-tag>
      </span>
      <span slot="action" slot-scope="text, record">
        <a @click="openEditModal(record)">编辑</a>
        <a-divider type="vertical" />
        <a-popconfirm title="确定要删除该菜单吗？" @confirm="handleDelete(record)">
          <a style="color: red">删除</a>
        </a-popconfirm>
      </span>
    </a-table>

    <a-modal
      :title="modalTitle"
      v-model="modalVisible"
      @ok="handleOk"
      :confirmLoading="modalLoading"
      destroyOnClose
    >
      <a-form :form="form">
        <a-form-item label="名称" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input v-decorator="['text', { rules: [{ required: true, message: '请输入名称' }] } ]" />
        </a-form-item>
        <a-form-item label="上一级菜单" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-tree-select
            v-decorator="['pid', { initialValue: 0 }]"
            :treeData="treeSelectData"
            placeholder="请选择父级菜单"
            allowClear
            treeDefaultExpandAll
            :dropdownStyle="{ maxHeight: '300px', overflow: 'auto' }"
          />
        </a-form-item>
        <a-form-item label="链接地址" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input v-decorator="['url']" placeholder="请输入链接地址" />
        </a-form-item>
        <a-form-item label="路由" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input v-decorator="['route']" placeholder="请输入路由" />
        </a-form-item>
        <a-form-item label="权限" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input v-decorator="['prem']" placeholder="请输入权限标识" />
        </a-form-item>
        <a-form-item label="是否为分类" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-radio-group v-decorator="['issort', { initialValue: 0 }]">
            <a-radio :value="1">分类</a-radio>
            <a-radio :value="0">菜单</a-radio>
          </a-radio-group>
        </a-form-item>
        <a-form-item label="排序" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input-number v-decorator="['sort', { initialValue: 0 }]" :min="0" style="width: 100%" />
        </a-form-item>
        <a-form-item label="菜单启用状态" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-radio-group v-decorator="['status', { initialValue: 1 }]">
            <a-radio :value="1">启用</a-radio>
            <a-radio :value="0">禁用</a-radio>
          </a-radio-group>
        </a-form-item>
        <a-form-item label="仅开发者可见" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-radio-group v-decorator="['isdev', { initialValue: 0 }]">
            <a-radio :value="1">开发者可见</a-radio>
            <a-radio :value="0">全部可见</a-radio>
          </a-radio-group>
        </a-form-item>
        <a-form-item label="说明" :labelCol="labelCol" :wrapperCol="wrapperCol">
          <a-input v-decorator="['tip']" placeholder="请输入说明" />
        </a-form-item>
      </a-form>
    </a-modal>
  </a-card>
</template>

<script>
import {
  getSysMenuTreeList,
  addSysMenu,
  editSysMenuById,
  deleteSysMenuById,
  getSysMenu
} from '@/api/common/api'

function convertMenuTree(list) {
  return (list || []).map(item => {
    const children = item.children && item.children.length > 0
      ? convertMenuTree(item.children)
      : item.childList && item.childList.length > 0
        ? convertMenuTree(item.childList)
        : []
    // 兼容多种父级字段名，强制补全 pid
    const pid = item.pid !== undefined ? item.pid : (item.parentId !== undefined ? item.parentId : (item.pId !== undefined ? item.pId : 0));
    return {
      ...item,
      pid,
      name: item.text,
      status: typeof item.status !== 'undefined' ? item.status : 1,
      statusLoading: false,
      children // 始终为数组
    }
  })
}

export default {
  name: 'VeBaseSysMenuList',
  data() {
    return {
      loading: false,
      menuTree: [],
      treeSelectData: [],
      columns: [
        { title: '名称', dataIndex: 'text', key: 'text' },
        { title: '链接地址', dataIndex: 'url', key: 'url' },
        { title: '路由', dataIndex: 'route', key: 'route' },
        { title: '权限标识符', dataIndex: 'prem', key: 'prem' },
        { title: '是否为分类', dataIndex: 'issort', key: 'issort', scopedSlots: { customRender: 'issort' } },
        { title: '排序', dataIndex: 'sort', key: 'sort' },
        { title: '菜单启用状态', dataIndex: 'status', key: 'status', scopedSlots: { customRender: 'status' } },
        { title: '仅开发者可见', dataIndex: 'isdev', key: 'isdev', scopedSlots: { customRender: 'isdev' } },
        { title: '说明', dataIndex: 'tip', key: 'tip' },
        { title: '操作', key: 'action', scopedSlots: { customRender: 'action' }, width: 140 }
      ],
      modalVisible: false,
      modalTitle: '新增菜单',
      modalLoading: false,
      form: this.$form.createForm(this),
      currentId: null,
      labelCol: { span: 6 },
      wrapperCol: { span: 16 }
    }
  },
  created() {
    this.loadMenuTree()
  },
  methods: {
    getCurrentAppId() {
      try {
        const userInfo = JSON.parse(localStorage.getItem('userInfo') || '{}')
        return userInfo.appId || ''
      } catch (e) {
        return ''
      }
    },
    async loadMenuTree() {
      this.loading = true
      try {
        const appId = this.getCurrentAppId()
        const res = await getSysMenuTreeList({ id: appId })
        this.menuTree = convertMenuTree(res.result || [])
        this.treeSelectData = this.buildTreeSelect(this.menuTree)
      } catch (error) {
        this.$message.error('加载菜单失败')
      } finally {
        this.loading = false
      }
    },
    buildTreeSelect(tree) {
      const loop = list =>
        list.map(item => ({
          title: item.text,
          value: Number(item.id),
          key: Number(item.id),
          children: item.children ? loop(item.children) : []
        }));
      // 只返回一个根节点，children为所有菜单
      return [{
        title: '顶级菜单',
        value: 0,
        key: 0,
        children: loop(tree)
      }];
    },
    openAddModal() {
      this.modalTitle = '新增菜单'
      this.currentId = null
      this.form.resetFields()
      this.form.setFieldsValue({ pid: 0, sort: 0, status: 1, issort: 0, isdev: 0 })
      this.modalVisible = true
    },
    async openEditModal(record) {
      if (!record) {
        this.$message.error('数据异常，无法编辑！')
        return
      }
      this.modalTitle = '编辑菜单'
      this.currentId = record.id
      this.form.resetFields()
      this.modalVisible = true
      // 每次都强制刷新菜单树数据，保证treeSelectData为最新
      await this.loadMenuTree()
      // 获取菜单详情并回填表单
      try {
        this.modalLoading = true
        const res = await getSysMenu({ id: record.id })
        if (res.success && res.result) {
          const menuData = res.result
          const currentId = Number(menuData.id);
          const parentId = Number(menuData.pid) < 0 ? 0 : Number(menuData.pid);
          this.$nextTick(() => {
            this.form.setFieldsValue({
              text: menuData.text,
              pid: parentId,
              url: menuData.url,
              route: menuData.route,
              prem: menuData.prem,
              issort: menuData.issort || 0,
              sort: menuData.sort || 0,
              status: menuData.status !== undefined ? menuData.status : 1,
              isdev: menuData.isdev || 0,
              tip: menuData.tip
            });
          });
        } else {
          this.$message.error('获取菜单详情失败')
        }
      } catch (error) {
        console.error('获取菜单详情失败:', error)
        this.$message.error('获取菜单详情失败')
      } finally {
        this.modalLoading = false
      }
    },
    handleOk() {
      this.form.validateFields(async (err, values) => {
        if (err) return
        this.modalLoading = true
        const appId = this.getCurrentAppId()
        values.appId = appId
        values.terminalid = 0
        // route未填写时强制为空字符串
        if (!values.route) {
          values.route = ''
        }
        // 新增菜单且选择的父菜单是顶级菜单，传pid:0
        if (!this.currentId && (values.pid === undefined || values.pid === null || values.pid === '' || values.pid === 0 || values.pid === '0')) {
          values.pid = 0
        }
        // 编辑顶级菜单时pid=-id
        if (this.currentId && (values.pid === 0 || values.pid === '0')) {
          values.pid = -Math.abs(Number(this.currentId))
        }
        try {
          if (this.currentId) {
            await editSysMenuById({ ...values, id: this.currentId })
            this.$message.success('修改成功')
          } else {
            await addSysMenu(values)
            this.$message.success('新增成功')
          }
          this.modalVisible = false
          this.loadMenuTree()
        } catch (error) {
          this.$message.error(this.currentId ? '修改失败' : '新增失败')
        } finally {
          this.modalLoading = false
        }
      })
    },
    async handleDelete(record) {
      if (!record || !record.id) {
        this.$message.error('删除失败，未获取到菜单ID')
        return
      }
      this.loading = true
      try {
        await deleteSysMenuById(record)
        this.$message.success('删除成功')
        this.loadMenuTree()
      } catch (error) {
        this.$message.error('删除失败')
      } finally {
        this.loading = false
      }
    },
    async onStatusChange(record, checked) {
      this.$set(record, 'statusLoading', true)
      try {
        const updateData = {
          id: record.id,
          status: checked ? 1 : 0,
          appId: this.getCurrentAppId(),
          terminalid: 0
        }
        await editSysMenuById(updateData)
        record.status = updateData.status
        this.$message.success(updateData.status ? '已启用' : '已禁用')
      } catch (error) {
        this.$message.error('状态更新失败')
      } finally {
        this.$set(record, 'statusLoading', false)
      }
    }
  }
}
</script>

<style scoped>
.table-operator {
  margin-bottom: 16px;
}
</style>